using System;
using GameFrameworkLibraly.BaseObjects;
using GameFrameworkLibraly.Helpers.GeometryHelpers;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input.Touch;

namespace GameFrameworkLibraly.Controls
{
    public class VolumeControl:Control
    {
        private readonly Texture2D _speakerphoneTexture;
        private readonly Texture2D _speakerphoneOffTexture;
        private readonly Texture2D _volumeBarFullTexture;
        private readonly Texture2D _volumeBarPartTexture;

        private Rectangle _speakerphoneRectangle;
        private Rectangle _volumeBarFullRectangle;
        private Rectangle _volumeBarPartRectangle;

        /// <summary>
        /// Creates a new instance of Volume Control
        /// </summary>
        /// <param name="game">Current game</param>
        /// <param name="speakerphoneTexture">Texture of speakerphone </param>
        /// <param name="speakerphoneOffTexture">Texture of muted speakerphone</param>
        /// <param name="volumeBarFullTexture">Texture of volume bar</param>
        /// <param name="volumeBarPartTexture">Texure of fore part of volume bar</param>
        /// <param name="destinationRectangle">Rectangle where the contol will be drawn</param>
        public VolumeControl(MyGame game, Texture2D speakerphoneTexture, Texture2D speakerphoneOffTexture, Texture2D volumeBarFullTexture, Texture2D volumeBarPartTexture, Rectangle destinationRectangle):base(game)
        {
            _speakerphoneTexture = speakerphoneTexture;
            _volumeBarPartTexture = volumeBarPartTexture;
            _volumeBarFullTexture = volumeBarFullTexture;
            _speakerphoneOffTexture = speakerphoneOffTexture;
            DestinationRectangle = destinationRectangle;

            RecalculateRectangles();
            DestinationRectangleChanged += VolumeControlDestinationRectangleChanged;
            VolumeLevelChanged += VolumeControlVolumeLevelChanged;
        }

        void VolumeControlVolumeLevelChanged(object sender, EventArgs e)
        {
            int volumeBarPartHeight = _speakerphoneRectangle.Height * _volumeLevel / 100;
            int volumeBarPartX = _speakerphoneRectangle.Top +
                                 (_speakerphoneRectangle.Height - volumeBarPartHeight) / 2;
            _volumeBarPartRectangle = new Rectangle(_speakerphoneRectangle.Right + 5,
                                                    volumeBarPartX,
                                                    (DestinationRectangle.Width - _speakerphoneRectangle.Width -20) * _volumeLevel / 100,
                                                    volumeBarPartHeight);
        }

        /// <summary>
        /// Recalculates rectangles for internal textures
        /// </summary>
        protected void RecalculateRectangles()
        {
            _speakerphoneRectangle = new Rectangle(DestinationRectangle.X + 5, DestinationRectangle.Y + 5,
                                                   DestinationRectangle.Height - 10, DestinationRectangle.Height - 10);
            _volumeBarFullRectangle = new Rectangle(_speakerphoneRectangle.Right + 5,
                                                    _speakerphoneRectangle.Top,
                                                    DestinationRectangle.Width - _speakerphoneRectangle.Width - 20,
                                                    _speakerphoneRectangle.Height);
            int volumeBarPartHeight = _speakerphoneRectangle.Height * _volumeLevel / 100;
            int volumeBarPartX = _speakerphoneRectangle.Top +
                                 (_speakerphoneRectangle.Height - volumeBarPartHeight) / 2;
            _volumeBarPartRectangle = new Rectangle(_speakerphoneRectangle.Right + 5,
                                                    volumeBarPartX,
                                                    (DestinationRectangle.Width - _speakerphoneRectangle.Width -20) * _volumeLevel / 100,
                                                    volumeBarPartHeight);
        }

        void VolumeControlDestinationRectangleChanged(object sender, EventArgs e)
        {
            RecalculateRectangles();
        }

        private int _oldVolumeLevel;
        private int _volumeLevel = 50;

        /// <summary>
        /// Returns current volume level in Range 0..100
        /// </summary>
        public int VolumeLevel
        {
            get { return _volumeLevel; }
        }

        /// <summary>
        /// Returns current volume level in Range 0..1
        /// </summary>
        public double VolumeLevelDouble
        {
            get { return _volumeLevel/100.0; }
        }

        /// <summary>
        /// Occures when Volume Level has been changed
        /// </summary>
        public event EventHandler VolumeLevelChanged;

        private void InvokeVolumeLevelChanged(EventArgs e)
        {
            EventHandler handler = VolumeLevelChanged;
            if (handler != null) handler(this, e);
        }


        #region Control

        /// <summary>
        /// Draws the control
        /// </summary>
        /// <param name="spriteBatch"></param>
        public override void Draw(SpriteBatch spriteBatch)
        {
            if(BackgroundTexture!=null)
                spriteBatch.Draw(BackgroundTexture,DestinationRectangle,BackColorFilter);
            spriteBatch.Draw(_volumeLevel != 0 ? _speakerphoneTexture : _speakerphoneOffTexture, _speakerphoneRectangle, ForeColor);
            spriteBatch.Draw(_volumeBarFullTexture, _volumeBarFullRectangle, ForeColor);
            spriteBatch.Draw(_volumeBarPartTexture, _volumeBarPartRectangle, ForeColor);
        }

        /// <summary>
        /// Updates state of the control
        /// </summary>
        /// <param name="gameTime"></param>
        public override void Update(GameTime gameTime)
        {
        }

        public override bool ProcessTouch(TouchLocation touchLocation)
        {
            if (!Enabled)
                return false;
            if (_speakerphoneRectangle.Contains(touchLocation.Position.ToPoint()) && touchLocation.State == TouchLocationState.Pressed)
            {
                if (_volumeLevel == 0 && _oldVolumeLevel != 0)
                    _volumeLevel = _oldVolumeLevel;
                else
                {
                    _oldVolumeLevel = _volumeLevel;
                    _volumeLevel = 0;
                }
                InvokeVolumeLevelChanged(EventArgs.Empty);
                return true;
            }
            if (_volumeBarFullRectangle.Contains(touchLocation.Position.ToPoint()))
            {
                _volumeLevel =(int)((touchLocation.Position.X - _volumeBarFullRectangle.Left)*100/_volumeBarFullRectangle.Width);
                if (_volumeLevel < 5)
                    _volumeLevel = 0;
                else if (_volumeLevel > 95)
                    _volumeLevel = 100;
                InvokeVolumeLevelChanged(EventArgs.Empty);
                return true;
            }

            return false;
        }

        #endregion
    }
}
